<?php


namespace app\platform\merchant\controller;


use app\common\controller\BaseController;
use app\common\model\Merchant;
use app\common\model\MerMenu;
use app\common\model\RenewalRecord;
use app\common\model\SysMerchantCategory;
use app\common\model\SysMerchantMenu;
use app\platform\system\service\AdminService;
use app\platform\system\validate\RenewalValidate;
use Carbon\Carbon;
use support\exception\BadException;
use support\Response;
use support\utils\RandomUtil;
use support\utils\Time;
use support\utils\UserUtil;
use think\db\exception\DataNotFoundException;
use think\db\exception\DbException;
use think\db\exception\ModelNotFoundException;
use think\facade\Db;

/**
 * 管理商户
 * Class MerchantController
 * @package app\platform\system\controller
 */
class MerchantController extends BaseController
{
    protected $model = Merchant::class;

    public function list()
    {
        $name = input('name', '');
        $category_id = input('category_id', '');
        $where = [];
        $name && $where[] = ['name', 'like', "%{$name}%"];
        $category_id && $where[] = ['category_id', '=', $category_id];
        $pageSize = intval(input('pageSize')) ?: DEFAULT_PAGE_LIMIT;
        $pageNo = intval(input('pageNo')) ?: DEFAULT_PAGE_NO;

        $count = $this->getModel()
            ->where($where)
            ->count();

        $data = $this->getModel()
            ->where($where)
            ->with([
                'category'
            ])
            ->limit(($pageNo - 1) * $pageSize, $pageSize)
            ->select()
            ->toArray();

        return $this->success($this->formatPage($count, $data));
    }

    public function add()
    {
        $data = request()->all();

        if (!$data['category_id']) {
            throw new BadException("请选择分类");
        }
        $cate = SysMerchantCategory::where(["id" => $data['category_id']])->find();
        $data['tenant_id'] = RandomUtil::simpleUUID();
        $data['expire_time'] = Carbon::now()->endOfDay()->add($cate['open_type'], $cate['open_time'])
            ->format(Time::DATE_TIME);
        $data['created_at'] = Time::now();

        $menuIds = [];
        $insertMenu = [];
        if ($cate['is_super_category']) {
            $menuIds = SysMerchantMenu::where(['menuStatus' => 0])->column('menuId');
        } else {
            if ($cate['menu_id_text']) {
                $menuIds = explode(',', $cate['menu_id_text']);
            }
        }
        foreach ($menuIds as $id) {
            $insertMenu[] = [
                'menu_id' => $id,
                'tenant_id' => $data['tenant_id'],
            ];
        }
        Db::transaction(function () use ($data, $insertMenu) {
            MerMenu::insertAll($insertMenu);
            $this->getModel()->insert($data);
        });
        return $this->success();
    }

    public function update()
    {
        $data = request()->all();
        $this->getModel()->where(['id' => $data['id']])->update($data);
        return $this->success();
    }

    public function getById()
    {
        $id = input('id');
        $data = $this->getModel()->where(['id' => $id])->find();
        return $this->success($data);
    }

    public function updateStatus()
    {
        $id = input('id');
        $status = input('status');
        $data = $this->getModel()->where(['id' => $id])->update([
            'status' => $status
        ]);
        return $this->success($data);
    }

    /**
     * 租户已经分配的菜单id
     * @return Response
     * @throws DataNotFoundException
     * @throws DbException
     * @throws ModelNotFoundException
     */
    public function listMenuIdsByMerId()
    {
        // 菜单反选数据[菜单反选只注重子节点，父节点不用返回，子节点都有父节点自然会选中]
        $tenant_id = input('tenant_id', "");
        if (!$tenant_id) {
            return $this->success();
        }
        $data = SysMerchantMenu::alias('a')
            ->join('t_mer_menu b', 'a.menuId=b.menu_id')
            ->where([
                'b.tenant_id' => $tenant_id,
                'b.menuStatus' => 0,
            ])
            ->order("a.sorted")
            ->field([
                'a.menuId',
                'a.parentId',
            ])
            ->select()
            ->toArray();
        $res = [];
        $hasChild = SysMerchantMenu::whereIn('parentId', array_column($data, 'menuId'))
            ->column('parentId');
        foreach ($data as $datum) {
            if (!in_array($datum['menuId'], $hasChild)) {
                $res[] = $datum['menuId'];
            }
        }
        return $this->success($res);
    }

    public function allocationMenu()
    {
        $tenantId = input('tenantId');
        $menuIds = input('menuIds');
        $inst = [];
        foreach ($menuIds as $id) {
            $inst[] = [
                'tenant_id' => $tenantId,
                'menu_id' => $id,
            ];
        }
        Db::transaction(function () use ($tenantId, $inst) {
            MerMenu::where(["tenant_id" => $tenantId])->delete();
            MerMenu::insertAll($inst);
        });
        return $this->success();
    }

    public function renewalRecord()
    {
        $tenant_id = input('tenant_id', "");
        $data = RenewalRecord::where(["tenant_id" => $tenant_id])->order("created_at", 'desc')->select();
        return $this->success($data);
    }

    public function renewal()
    {
        RenewalValidate::goCheck(input());
        Db::transaction(function () {
            $open_time = input('open_time', "");
            $name = input('name', "");
            $open_type = input('open_type', "");
            $tenant_id = input('tenant_id', "");

            $operation_by = AdminService::getAdminName(UserUtil::getUid());

            Merchant::where(["tenant_id" => $tenant_id])
                ->update([
                    'expire_time' => Carbon::now()
                        ->endOfDay()
                        ->add($open_type, $open_time)
                        ->format(Time::DATE_TIME)
                ]);
            RenewalRecord::insert([
                "tenant_id" => $tenant_id,
                "tenant_name" => $name,
                "open_time" => $open_time,
                "open_type" => $open_type,
                "operation_by" => $operation_by,
                "operation_uid" => UserUtil::getUid(),
                "created_at" => Time::now(),
                "remark" => input('remark', ""),
            ]);
        });

        return $this->success();
    }
}